package controllers

import (
	"github.com/astaxie/beego"
	"time"
	"strconv"
	"strings"
	"math/rand"
	"image"
	"os"
	"image/jpeg"
	"image/png"
	"log"
	"github.com/BurntSushi/graphics-go/graphics"
	"fmt"
	"github.com/hundredlee/wechat_pusher/task"
	"github.com/hundredlee/wechat_pusher/enum"
	wxmodels "github.com/hundredlee/wechat_pusher/models"
	wxutils "github.com/hundredlee/wechat_pusher/utils"
	"net/url"
	"encoding/base64"
	"github.com/astaxie/beego/httplib"
	"errors"
	"crypto/hmac"
	"crypto/sha1"
)

type JsonReturnData_Message struct {
	Code int
	Data string
}

func Json_Message(c *beego.Controller, code int, data string) {
	json_error := JsonReturnData_Message{Code:code, Data:data }
	c.Data["json"] = &json_error
	c.ServeJSON()
	c.StopRun()
}

func Message(c *beego.Controller, redirectURL string, message string, ExtraInfo string, back bool) {
	c.Data["Message"] = message
	c.Data["TargetURL"] = redirectURL
	if back {
		c.Data["script"] = `<script type="text/javascript">
		function back(secs) {
		var jumpTo = document.getElementById('jumpTo');
		jumpTo.innerHTML = secs;
		if (--secs > 0) {
		setTimeout("back(" + secs + ")", 1000);
		}
else {
history.go(-1);
}
}
back(3);
</script>`
	} else {
		c.Data["script"] = fmt.Sprintf(`<script type="text/javascript">
		countDown(3, "%s");
	</script>`, redirectURL)
	}
	c.TplName = "message.html"
	c.Render()
	c.StopRun()
}


// LoadImage decodes an image from a file.
func LoadImage_FromPath(path string) (img image.Image, err error) {
	file, err := os.Open(path)
	if err != nil {
		return
	}
	defer file.Close()
	img, _, err = image.Decode(file)
	if err != nil {
		img, err = jpeg.Decode(file)
	}
	return
}

func SaveImage(path string, img image.Image) (err error) {
	// 需要保存的文件
	imgfile, err := os.Create(path)
	defer imgfile.Close()
	// 以PNG格式保存文件
	err = png.Encode(imgfile, img)
	if err != nil {
		log.Fatal(err)
	}
	return
}

func GenerateTumbnail(filepath string, structName string, Id int64, width int, height int) {
	path := beego.AppConfig.String("uploadspath")
	directory := "/thumbnail/" + strings.ToLower(structName)
	totalPath := path + directory + "/" + strconv.FormatInt(Id, 10) + "_" + strconv.Itoa(width) + "x" + strconv.Itoa(height) + ".png"
	os.MkdirAll(path + directory, 0777)
	src, err := LoadImage_FromPath(filepath)
	if err != nil {
		return
	}
	// 缩略图的大小
	dst := image.NewRGBA(image.Rect(0, 0, width, height))
	// 产生缩略图
	err = graphics.Thumbnail(dst, src)
	if err != nil {
		return
	}
	SaveImage(totalPath, dst)
}
func TacleUeditor(c *beego.Controller) {
	action := c.GetString("action")
	if action == "config" {
		c.Data["json"] = map[string]interface{}{
			"imageUrl": "http://localhost:8082/article/multitextimageUp?action=uploadimage",
			"imagePath": "/",
			"imageFieldName": "upfile",
			"imageMaxSize": 2048,
			"imageActionName":"uploadimage",
			"imagePathFormat":"/ueditor/php/upload/image/{yyyy}{mm}{dd}/{time}{rand:6}",
			"imageUrlPrefix":"",
			"imageAllowFiles":[]string{".png", ".jpg", ".jpeg", ".gif", ".bmp"}}

		c.ServeJSON()
		c.StopRun()
	}
	if action != "uploadimage" {
		Json_Message(c, 1, "not surport" + action)
	}
}

type Data_Alarm struct {
	Position   wxmodels.Raw `json:"position"`
	Name       wxmodels.Raw `json:"devicename"`
	Type       wxmodels.Raw `json:"devicetype"`
	AlarmValue wxmodels.Raw `json:"alarmvalue"`
	AlarmLevel wxmodels.Raw `json:"alarmlevel"`
}

func SendToWX(position, name, deviceType, alarmReason, url string, alarmLevel int, openIds []string) {
	var tasks []task.Task
	AlarmColor := "#173177"
	if alarmLevel > 1 {
		AlarmColor = "##FF0000"
	}
	//openIds := []string{"oM7kMwu0KozK7qEAc33KHDnq3L_M", "oM7kMwnl3LGc3Xs-Y3FxObrH6Q8Y", "oM7kMwoYenNeKJjPbn0qQpVDui5Y"}
	tasks = make([]task.Task, len(openIds))
	mess := wxmodels.Message{
		ToUser:     "oM7kMwu0KozK7qEAc33KHDnq3L_M",
		TemplateId: "Y8jgZ4nu4p5Ytg2eysFhASn_OYfMPyVfLgeiNm4-aTU",
		Url:        url,
		Data: Data_Alarm{
			Position:   wxmodels.Raw{position, AlarmColor},
			Name: wxmodels.Raw{name, AlarmColor},
			Type:  wxmodels.Raw{deviceType, AlarmColor},
			AlarmValue:wxmodels.Raw{alarmReason, AlarmColor},
			AlarmLevel:wxmodels.Raw{strconv.Itoa(alarmLevel), AlarmColor},
		},
	}

	for index, v := range openIds {
		task := task.TemplateTask{}
		mess.ToUser = v
		task.SetTask(mess)
		tasks[index] = &task
	}

	wxutils.NewPush(&wxutils.Push{
		Tasks:tasks,
		TaskType:enum.TASK_TYPE_TEMPLATE,
		Retries:5,
		BufferNum:10,
	}).RunRightNow("wxtask")
}

func Sendsms(position, devicename, value, phone string, level int) (error) {
	accessSecret := "Kr3zrf4VJQe9pjCoeAT9Eex6NZpbPC"
	//accessSecret = "testId"
	Signature := ""
	AccessKeyId := "LTAIAYKBapO9xKCA"
	Action := "SendSms"
	Format := "JSON"
	OutId := "123"
	PhoneNumbers := phone
	RegionId := "cn-hangzhou"
	SignName := "蒋兴权"
	SignatureMethod := "HMAC-SHA1"
	SignatureNonce := RandString(12)
	SignatureVersion := "1.0"
	TemplateCode := "SMS_99120014"
	TemplateParam := fmt.Sprintf(`{"position":"%s","devicename":"%s","value":"%s","level":"%d"}`, position, devicename, value, level)
	fmt.Println(TemplateParam)
	TemplateParam = strings.Replace(TemplateParam, " ", ";", -1)
	Timestamp := time.Now().UTC().Format("2006-01-02T15:04:05Z")
	Version := "2017-05-25"

	sine_url := fmt.Sprintf(`AccessKeyId=%s&Action=%s&Format=%s&OutId=%s&PhoneNumbers=%s&RegionId=%s&SignName=%s&SignatureMethod=%s&SignatureNonce=%s&SignatureVersion=%s&TemplateCode=%s&TemplateParam=%s&Timestamp=%s&Version=%s`, AccessKeyId, Action, Format, OutId, PhoneNumbers, RegionId, SignName, SignatureMethod, SignatureNonce, SignatureVersion, TemplateCode, TemplateParam, Timestamp, Version)
	//sine_url = `AccessKeyId=testId&Action=SendSms&Format=XML&OutId=123&PhoneNumbers=15300000001&RegionId=cn-hangzhou&SignName=阿里云短信测试专用&SignatureMethod=HMAC-SHA1&SignatureNonce=45e25e9b-0a6f-4070-8c85-2956eda1b466&SignatureVersion=1.0&TemplateCode=SMS_71390007&TemplateParam={"customer":"test"}&Timestamp=2017-07-12T02:42:19Z&Version=2017-05-25`
	sine_url = url.PathEscape(sine_url)
	sine_url = strings.Replace(sine_url, ":", "%3A", -1)

	fmt.Println(sine_url)

	sine_url = "GET&" + getSpecialURLENCODE("/") + "&" + getSpecialURLENCODE(sine_url)
	accessSecretValue := sign_sha1(accessSecret + "&", sine_url)
	fmt.Println(accessSecretValue)
	Signature = getSpecialURLENCODE(base64.StdEncoding.EncodeToString(accessSecretValue))

	urls := fmt.Sprintf(`http://dysmsapi.aliyuncs.com?Signature=%s&AccessKeyId=%s&Action=%s&Format=%s&OutId=%s&PhoneNumbers=%s&RegionId=%s&SignName=%s&SignatureMethod=%s&SignatureNonce=%s&SignatureVersion=%s&TemplateCode=%s&TemplateParam=%s&Timestamp=%s&Version=%s`, Signature, AccessKeyId, Action, Format, OutId, PhoneNumbers, RegionId, SignName, SignatureMethod, SignatureNonce, SignatureVersion, TemplateCode, TemplateParam, Timestamp, Version)

	fmt.Println(accessSecret)
	fmt.Println(Signature)
	fmt.Println(urls)
	fmt.Println(url.QueryEscape(urls))
	result := AliSmsReturn{}
	httplib.Get(urls).SetTimeout(5 * time.Second, 5 * time.Second).Debug(true).ToJSON(&result)
	if result.Message == "OK" {
		return nil
	}

	return errors.New("send message wrong" + result.Message)
}

type AliSmsReturn struct {
	Message   string
	RequestId string
	BizId     string
	Code      string
}

func sign_sha1(key string, data string) []byte {
	h := hmac.New(sha1.New, []byte(key))
	h.Write([]byte(data))
	return h.Sum(nil)
}

func getSpecialURLENCODE(sine_url string) string {
	sine_url = url.QueryEscape(sine_url)
	sine_url = strings.Replace(sine_url, "+", "%20", -1)
	sine_url = strings.Replace(sine_url, "*", "%2A", -1)
	sine_url = strings.Replace(sine_url, "%7E", "~", -1)
	return sine_url
}

func RandString(length int) string {
	rand.Seed(time.Now().UnixNano())
	rs := make([]string, length)
	for start := 0; start < length; start++ {
		t := rand.Intn(3)
		if t == 0 {
			rs = append(rs, strconv.Itoa(rand.Intn(10)))
		} else if t == 1 {
			rs = append(rs, string(rand.Intn(26) + 65))
		} else {
			rs = append(rs, string(rand.Intn(26) + 97))
		}
	}
	return strings.Join(rs, "")
}

func GetPassword(passorigin string) string {
	return passorigin
}